package p16_切点匹配;

import org.springframework.aop.aspectj.AspectJExpressionPointcut;
import org.springframework.transaction.annotation.Transactional;

/**
 * 切点类提供了匹配方法，判断指定的方法是否与该切点匹配，并返回一个boolean值
 * 由于所有bean都被spring管理了，spring就能知道bean中的方法信息，将来遍历这些方法时，就知道哪些方法需要被增强
 */
public class _1_PointCutMatches {
    public static void main(String[] args) throws NoSuchMethodException {
        //准备切点，并设置切点表达式
        AspectJExpressionPointcut pt1 = new AspectJExpressionPointcut();
        pt1.setExpression("execution(* foo())");
        //匹配成功，打印true
        System.out.println(pt1.matches(Target.class.getMethod("foo"), Target.class));
        //匹配失败，打印false
        System.out.println(pt1.matches(Target.class.getMethod("bar"), Target.class));

        //也可以匹配方法上的注解
        AspectJExpressionPointcut pt2 = new AspectJExpressionPointcut();
        pt2.setExpression("@annotation(org.springframework.transaction.annotation.Transactional)");
        //匹配失败，打印false
        System.out.println(pt2.matches(Target.class.getMethod("foo"), Target.class));
        //匹配成功，打印true
        System.out.println(pt2.matches(Target.class.getMethod("bar"), Target.class));

        /**
         * 以上的匹配规则，仅作用于方法，而@Transactional能作用于接口，类，方法上，是怎么实现的呢？
         */
    }


    static class Target {
        public void foo() {

        }

        @Transactional
        public void bar() {

        }
    }
}
